(function($) {

	$.fn.test = function(testDataJSON, options) {

		var data = testDataJSON;
		var questions = data.questions;
		var questionsCount = questions.length;
		var currentQuestionIndex = 1;
		var markedQuestions = {};
		var answeredQuestions = {};
		var reviewQuestions = new Array();
		var reviewQuestionsWrapper = {};


		var plugin = this;

		var defaultSettings = {
			nextQuestionText : "Next",
			prevQuestionText : "Previous",
			randomSortQuestions : true,
			draggable: {
      			cursor: 'move',
      			helper: 'clone',
      			revert: 'invalid',
      			zIndex: 10000,
      			start: null
    		}
		};

		plugin.config = $.extend(defaultSettings, options);

		var questionNoDiv = $("<div/>").addClass("span3 currentQuestion");
		var testNameDiv = $("<div/>").addClass("span6").addClass("testName");
		
		var timeRemainingDiv = $("<div/>").addClass("span3");
		timeRemainingDiv.countdown({until: +600});

		var testScreenHeaderDiv = $("<div/>").addClass("row-fluid testScreenHeader");
		testScreenHeaderDiv.append(questionNoDiv, testNameDiv, timeRemainingDiv);

		$(".test").append(testScreenHeaderDiv);
		$(".test").append($("<div/>").addClass("row-fluid testArea"));


		var selector = "test";

		var viewOnlyMarked = false;

		var reviewedOnce = false;

		plugin.method = {

		 	setUpTest : function() {
	 			

				$(".testName").html(data.info.name);
				var questionsList = $('<ul class="questions"></ul>');
				for ( i=0 ; i < questionsCount; i++ ) {
					var question = questions[i];
					var questionLI = $('<li class="question" id="question' + (i+1) +'"></li>');
					questionLI.append('<h3>' + question.q + '</h3>');

					var inputName = "question" + (i+1);
					
					var answers = question.a;
					if ( question.type == "SingleSelect") {
						var answersList = $('<ul class="answers"></ul>');
						for ( j in answers ) {
							var answer = answers[j];
							var optionId = inputName + "_" + j.toString();
							var optionHolder = $('<div class="option"></div>');
                           	var input = '<input id="' + optionId + '" name="' + inputName
                            + '" type="radio" />';
                            var optionLabel = '<label for="' + optionId + '">' + answer.option + '</label>';
                            //optionLabel.append(input);
                            var answerContent = $("<li></li>");
                           // answerContent.append(optionHolder.append(input).append(optionLabel));
                            answerContent.append(optionHolder.append(input, optionLabel));
                            answersList.append(answerContent);
                        };
                        questionLI.append("<br>");
                        questionLI.append(answersList).hide();
						questionsList.append(questionLI);  
                    };

                    if ( question.type == "MultiSelect") {
                    	var answersList = $('<ul class="answers"></ul>');
                    	for ( j in answers ) {
							var answer = answers[j];
							var optionId = inputName + "_" + j.toString();
							var optionHolder = $('<div class="row-fluid"></div>');
							var input = '<div class="span1"><input id="' + optionId + '" name="' + inputName
                            + '" type="checkbox" /></div>';
                            var optionLabel = '<div class="span11"><label for="' + optionId + '">' + answer.option + '</label></div>';
                            var answerContent = $("<li></li>");
                            answerContent.append(optionHolder.append(input).append(optionLabel));
                            answersList.append(answerContent);
                        };
                        questionLI.append("<br>");
                        questionLI.append(answersList).hide();
						questionsList.append(questionLI);    
                    };

                   	if ( question.type == "Match" ) {
                    	var answersHolder = $('<div class="row-fluid"></div>');
                    	var lhsGroup = $('<div class="span6"/>');
                    	var rhsGroup = $('<div class="span6"/>');
                    	var answersLHSList = $('<ul class="answers match"></ul>');
                    	var answersRHSList = $('<ul id="sortable" class="answers match"></ul>');

                    	for ( j in answers) {
                    		var answer = answers[j];
                    		
                    		var grp = answer.group;
	                    	if (grp == "Group1") {
	                    		var answerContent = $("<li class='ui-state-default'>"+answer.option+"</li>");
	                     		answersLHSList.append(answerContent);
	                    	}else if (grp == "Group2") {
	                    		var answerContent = $("<li class='ui-state-default'>"+answer.option+"</li>");
	                    		answersRHSList.append(answerContent);	
	                    	}else {
	                    		alert("OOPS , TEST DEVELOPER WAS DRUNK!!!!");
	                    	}
                    	};

                    
                    	lhsGroup.append(answersLHSList);
                    	rhsGroup.append(answersRHSList);
                     	answersHolder.append(lhsGroup).append(rhsGroup);
                     	
                     	answersRHSList.sortable({
							placeholder: "ui-state-highlight"
						});
						answersRHSList.disableSelection();


                    	questionLI.append(answersHolder).hide();
                    	questionsList.append(questionLI); 
                    } 
				};
				$(".testArea").append(questionsList);
				var btnHolder = $('<div class="btnHolder control-group"><div class="controls" ><a href="#" class="btn btn-primary prev" style="margin-left:2px">Previous</a><a href="#" class="btn btn-primary next" style="margin-left:2px">Next</a><a href="#" class="btn btn-primary review" style="margin-left:2px">Review</a><a href="#" class="btn btn-primary mark" style="margin-left:2px">Mark</a></div></div>')
		 		$(".testArea").append(btnHolder);

		 		$(".next").bind("click", function() {
		 			plugin.method.showNextQuestion();
		 		});

		 		$(".prev").bind("click", function() {
		 			plugin.method.showPrevQuestion();
		 		});

		 		$(".mark").bind("click", function() {
		 			plugin.method.toggleMarkQuestion();
		 		});

		 		$(".review").bind("click", function() {
		 			plugin.method.reviewQuestions();
		 		});

		 		$(".review-marked").live("click", function() {
		 			viewOnlyMarked = true;		

		 			//Hide the review Screen holder
		 			$(".testReviewArea").hide();

		 			//Figure out the first marked question
		 			for (i = 0; i <questionsCount; i++) {
		 				if(markedQuestions.hasOwnProperty(i+1)) {
		 					plugin.method.goToQuestion(i+1);
		 					break;
		 				}	
		 			}
		 			
		 			$(".currentQuestion").show();
		 			$('.testArea').show();
		 		});

		 	},
		 	
		 	startTest : function() {
				var firstQuestion = $('#' + selector + ' .questions li').first();
				if (firstQuestion.length) {
					firstQuestion.fadeIn(500);
				}
				questionNoDiv.html("Question " + currentQuestionIndex  + " of " + questionsCount );
		 	},

		 	showNextQuestion : function() {
		 		if ( currentQuestionIndex == questionsCount )
		 			return;
		 		if (viewOnlyMarked == false) {
		 			var currentQuestion = $('#' + selector + ' .questions .question').eq(currentQuestionIndex-1);
		 			currentQuestionIndex++;		 		
		 			var nextQuestion = $('#' + selector + ' .questions .question').eq(currentQuestionIndex-1);
			 		if(nextQuestion.length)  {
			 			//Hide the current question
			 			currentQuestion.hide();
			 			//Show the next question
			 			nextQuestion.fadeIn(500);
			 			nextQuestion.css('opacity','100');
			 			plugin.method.updateView();
			 		}
		 		}else {
		 			plugin.method.goToNextMarkedQuestion();
		 		}

		 		questionNoDiv.html("Question " + currentQuestionIndex  + " of " + questionsCount );
		 	},

		 	showPrevQuestion : function() {
		 		if ( currentQuestionIndex == 1)
		 			return;
		 		var currentQuestion = $('#' + selector + ' .questions .question').eq(currentQuestionIndex-1);
		 		currentQuestionIndex--;		 		
		 		var prevQuestion = $('#' + selector + ' .questions .question').eq(currentQuestionIndex-1);
		 		if(prevQuestion.length)  {
		 			//Hide the current question
		 			currentQuestion.hide();
		 			//Show the previous question
		 			prevQuestion.fadeIn(500);
		 			prevQuestion.css('opacity','100');
		 			plugin.method.updateView();
		 		}

		 		questionNoDiv.html("Question " + currentQuestionIndex  + " of " + questionsCount );
		 	},

		 	goToQuestion : function(questionNumber) {
		 		//Hide the question that the user was looking at when he clicked on review
		 		var currentQuestion = $('#' + selector + ' .questions .question').eq(currentQuestionIndex-1);
		 		currentQuestion.hide();

		 		//Set the question Number as the currentQuestionIndex
		 		currentQuestionIndex = questionNumber;
		 		currentQuestion = $('#' + selector + ' .questions .question').eq(currentQuestionIndex-1);
		 		currentQuestion.fadeIn(500);
		 		currentQuestion.css('opacity','100');
		 		plugin.method.updateView();
		 	},

		 	goToNextMarkedQuestion : function() {
		 		for ( i = currentQuestionIndex; i < questionsCount; i++ ) {
		 			if(markedQuestions.hasOwnProperty(i+1)) {
		 				plugin.method.goToQuestion(i+1);
		 				break;
		 			}		
		 		}
		 	},

		 	toggleMarkQuestion : function() {
		 		var markBtn = $(".btnHolder .controls .mark");
		 		if (markedQuestions.hasOwnProperty(currentQuestionIndex)) {
		 			delete markedQuestions[currentQuestionIndex];
		 			markBtn.removeClass("btn-success").addClass("btn-primary");
		 			markBtn.html("Mark");
		 		}else {
		 			markedQuestions[currentQuestionIndex] = "1";
		 			markBtn.removeClass("btn-primary").addClass("btn-success");
		 			markBtn.html("Unmark");
		 		}
		 	},

		 	updateView : function() {
		 		var markBtn = $(".btnHolder .controls .mark");
		 		if (markedQuestions.hasOwnProperty(currentQuestionIndex)) {
		 			markBtn.removeClass("btn-primary").addClass("btn-success");
		 			markBtn.html("Unmark");
		 		}else { 
		 			markBtn.removeClass("btn-success").addClass("btn-primary");
		 			markBtn.html("Mark");
		 		}
		 	},

		 	reviewQuestions : function() {
		 		//Set to defaults
		 		viewOnlyMarked = false;
		 		reviewQuestions = new Array();
		 		reviewQuestionsWrapper = {};

		 		for (i = 0; i <questionsCount; i++) {
		 			var question = questions[i];
		 			if(markedQuestions.hasOwnProperty(i+1)) {
		 				//Question is marked
		 				question.marked = "yes";
		 			}
		 			if(answeredQuestions.hasOwnProperty(i+1)) {
		 				question.complete = "yes";
		 			}
		 			reviewQuestions.push(question);
		 		}

		 		reviewQuestionsWrapper["questions"] = reviewQuestions;

		 		var src = $("#review-questions-tmpl").html();
 				var template =  Handlebars.compile(src);

		 		$('.testArea').hide();
		 		if (reviewedOnce == false) {
		 			$(".test").append($("<div/>").addClass("row-fluid testReviewArea"));
		 			reviewedOnce = true;
		 		}else {

		 			$(".testReviewArea").show();
		 			$(".testReviewArea").empty();
		 		}		
		 		$(".testReviewArea").load("../test/review_test.html", function() {
		 			//Hide the current Question	Div in the Header
		 			$(".currentQuestion").hide();

		 			$(".testReviewArea #review").append(template(reviewQuestionsWrapper));
				});

		 	},

		 	finishTest : function() {
		 		alert("Finished the test");
		 	},

		 };

		 plugin.method.setUpTest();
		 plugin.method.startTest();

	};	
})(jQuery); 